#File System Monitor
#coding:utf-8
import os
from tl import *


class Bag(object):
    """docstring for Bag"""
    def __init__(self, systeminfo):
        super(Bag, self).__init__()
        self.systeminfo = systeminfo#1 = Linux; 2 = Windows
        self.m_strWatchedDir = ""
        if systeminfo == 2:
            pass
            '''
            #WinAPI__INIT
            self.m_OVERLAPPED = OVERLAPPED()
            self.CreateFile = ctypes.windll.LoadLibrary("kernel32.dll").CreateFileA
            self.ReadDirectoryChangesW = ctypes.windll.LoadLibrary("kernel32.dll").ReadDirectoryChangesW
            #self.ReadDirectoryChangesW = ctypes.CDLL("kernel32.dll").ReadDirectoryChangesW
            self.CreateThread = ctypes.windll.LoadLibrary("kernel32.dll").CreateThread
            '''
    def BindFloder(self,path,space = 600):
        self.m_strWatchedDir = path
    def Verify(self,path):
        floders,files = gci(path)
        if floders == []:
            if os.path.isfile(os.path.join(path,"msvn")):
                results = self.__ContarstFloderBag(files,path)
            else:
                self.__CreateFloderBag(files,path)
        else:
            for i in floders:
                self.Verify(i)
    def __CreateFloderBag(self,files,path):
        Bag = {}
        for i in files:
            FileName = i[i.rindex("\\")+1:]
            md5 = GetFileMd5(i)
            ctime,mtime = GetFileCMTime(i)
            Bag[FileName] = "%s||%s||%s"%(str(md5),str(ctime),str(mtime))
        with open(os.path.join(path,"msvn"),"wb") as f:
            f.write(str(Bag))
    def __ContarstFloderBag(self,files,path):
        warrning = 0#多少个文件发生了修改
        with open(os.path.join(path,"msvn"),"rb") as f:
            Bag = eval(str(f.read()))#危险代码！
            #先验证包内数据
            for FileName in Bag:
                split = Bag[FileName].split("||")
                old_md5 = split[0]
                old_ctime = split[1]
                old_mtime = split[2]
                ctime,mtime = GetFileCMTime(os.path.join(path,FileName))
                if ctime != old_ctime or mtime != old_mtime:
                    new_md5 = GetFileMd5(os.path.join(path,FileName))
                    if str(new_md5) !=old_md5:
                        #文件发生变
                        print "File Changed:"+str(FileName)
                        warrning+=1
                        pass
        if warrning != 0:
            return 0
        else:
            return warrning
    def VerifyBag(self,path,session,bag):
        pass


    #因为代码实在蠢，所以选择放弃
'''
    def __Minitor_Windows(self):
        ThreadId = ctypes.c_int()
        lpFunc = ctypes.CFUNCTYPE(ctypes.c_int)

        #m_hThread = self.CreateThread(0,0,lpFunc(self.__Minitor_Windows_ThreadProc),0,0,ThreadId)

        m_hThread = threading.Thread(target=self.__Minitor_Windows_ThreadProc)
        m_hThread.start()
        m_hThread.join()

        print m_hThread,ThreadId
        if ThreadId == 0:
            return False
        else:
            return True
    def __Minitor_Windows_ThreadProc(self):
        print "1"
        pNotify = _FILE_NOTIFY_INFORMATION()
        dwBytesReturned = ctypes.c_int()
        hDir = self.CreateFile(self.m_strWatchedDir ,(GENERIC_READ|GENERIC_WRITE),(FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE),0,OPEN_EXISTING,FILE_FLAG_BACKUP_SEMANTICS,0)
        print hDir
        if hDir == -1:
            return 0
        while True:
            rdc = self.ReadDirectoryChangesW(hDir,ctypes.addressof(pNotify),1024,1,(FILE_NOTIFY_CHANGE_FILE_NAME|FILE_NOTIFY_CHANGE_DIR_NAME|FILE_NOTIFY_CHANGE_ATTRIBUTES|FILE_NOTIFY_CHANGE_SIZE|FILE_NOTIFY_CHANGE_LAST_WRITE|FILE_NOTIFY_CHANGE_LAST_ACCESS|FILE_NOTIFY_CHANGE_CREATION|FILE_NOTIFY_CHANGE_SECURITY),dwBytesReturned,self.m_OVERLAPPED,0)
            print rdc,ctypes.addressof(pNotify)
            if rdc:
                if pNotify.NextEntryOffset !=0 :
                    FileNames = pNotify.FileName
                else:
                    FileNames = pNotify.FileName
                FileNames = C_ByteArrayToString(FileNames)
                if pNotify.Action == FILE_ACTION_ADDED: print(("ADD:%s"%FileNames))#ADD
                if pNotify.Action == FILE_ACTION_REMOVED:print(("REMOVE:%s"%FileNames))#REMOVE
                if pNotify.Action == FILE_ACTION_RENAMED_NEW_NAME:print(("RENAME:%s"%FileNames)) #RENAME_NEW
                if pNotify.Action == FILE_ACTION_RENAMED_OLD_NAME:print(("REMOVE_OLD:%s"%FileNames))#RENAME_OLD
                if pNotify.Action == FILE_ACTION_MODIFIED:print(("EditFile:%s"%FileNames))#EditFile
                del pNotify,dwBytesReturned
                pNotify = _FILE_NOTIFY_INFORMATION()
                dwBytesReturned = ctypes.c_int()
                self.m_OVERLAPPED = OVERLAPPED()
            else:
                break
    '''

if __name__ == '__main__':
    a = Bag(1)
    a.Verify("D:\\TEST")
    print GetFileMd5("D:\\TEST\\123.txt")
